<script setup lang="ts">
import { ref, computed, watch, onMounted } from 'vue'
import {
	UploadOutlined,
	DeleteOutlined,
	PlayCircleOutlined,
	RollbackOutlined,
	EyeOutlined
} from '@ant-design/icons-vue'
import { message } from 'ant-design-vue'

interface Props {
	modelValue?: string
	showOnly?: boolean
	maxSize?: number // 最大文件大小，单位MB
	accept?: string // 接受的文件类型
}

const props = withDefaults(defineProps<Props>(), {
	modelValue: '',
	showOnly: false,
	maxSize: 50, // 默认50MB
	accept: 'video/*'
})

const emit = defineEmits<{
	'update:modelValue': [value: string | null]
	'file-change': [file: File | null]
}>()

// 响应式数据
const videoUrl = ref('')
const originalVideoUrl = ref<string | null>(null) // 保存原始视频URL用于撤回
const isUploading = ref(false)
const fileInputRef = ref<HTMLInputElement>()
const previewVisible = ref(false)

// 计算属性
const hasVideo = computed(() => !!videoUrl.value && !videoUrl.value.startsWith('data:'))
const isDefaultImage = computed(() => videoUrl.value.startsWith('data:'))
const canRollback = computed(() => {
	// 只有当有原始视频且当前状态与原始状态不同时才显示撤回
	return originalVideoUrl.value && videoUrl.value !== originalVideoUrl.value
})

// 辅助函数
const generateDefaultImage = () => {
	// 创建一个简单的SVG作为默认图片（使用英文文本避免编码问题）
	const svg = `
    <svg width="200" height="200" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
      <rect width="200" height="200" fill="#F3F4F6"/>
      <rect x="50" y="30" width="100" height="140" fill="#D8D9DA"/>
    </svg>
  `
	return `data:image/svg+xml;base64,${btoa(svg)}`
}

const resetFileInput = () => {
	if (fileInputRef.value) {
		fileInputRef.value.value = ''
	}
}

const processVideoFile = (file: File) => {
	isUploading.value = true

	try {
		// 创建临时URL用于预览
		const objectUrl = URL.createObjectURL(file)
		videoUrl.value = objectUrl

		// 发出事件
		emit('update:modelValue', objectUrl)
		emit('file-change', file)

		// message.success('视频上传成功')
	} catch (error) {
		console.error('视频处理失败:', error)
		message.error('视频处理失败，请重试')
	} finally {
		isUploading.value = false
		resetFileInput()
	}
}

// 事件处理函数
const handleFileSelect = (event: Event) => {
	if (props.showOnly) return

	const target = event.target as HTMLInputElement
	const file = target.files?.[0]

	if (!file) return

	// 文件类型验证
	if (!file.type.startsWith('video/')) {
		message.error('请选择视频文件')
		resetFileInput()
		return
	}

	// 文件大小验证
	const fileSizeMB = file.size / (1024 * 1024)
	if (fileSizeMB > props.maxSize) {
		message.error(`文件大小不能超过 ${props.maxSize}MB`)
		resetFileInput()
		return
	}

	// 处理文件
	processVideoFile(file)
}

const handleUploadClick = () => {
	if (props.showOnly) return
	fileInputRef.value?.click()
}

const handleDelete = () => {
	if (props.showOnly) return

	// 清理URL对象
	if (videoUrl.value.startsWith('blob:')) {
		URL.revokeObjectURL(videoUrl.value)
	}

	videoUrl.value = generateDefaultImage()
	emit('update:modelValue', null)
	emit('file-change', null)
	// message.success('视频已删除')
}

const handleRollback = () => {
	if (props.showOnly) return

	if (originalVideoUrl.value) {
		// 清理当前URL对象
		if (videoUrl.value.startsWith('blob:')) {
			URL.revokeObjectURL(videoUrl.value)
		}

		videoUrl.value = originalVideoUrl.value
		emit('update:modelValue', originalVideoUrl.value)
		emit('file-change', null) // 撤回时没有新文件
		// message.success('已撤回修改')
	}
}

const showPreview = () => {
	if (hasVideo.value) {
		previewVisible.value = true
	}
}

const handlePreviewCancel = () => {
	previewVisible.value = false
}

// 初始化
onMounted(() => {
	if (props.modelValue) {
		videoUrl.value = props.modelValue
		originalVideoUrl.value = props.modelValue
	} else {
		videoUrl.value = generateDefaultImage()
	}
})

// 监听modelValue变化
watch(
	() => props.modelValue,
	newValue => {
		if (newValue) {
			videoUrl.value = newValue
		} else {
			videoUrl.value = generateDefaultImage()
		}
	}
)
</script>

<template>
	<div class="relative w-30 h-30 border border-gray-300 rounded overflow-hidden bg-gray-50">
		<!-- 视频预览 -->
		<template v-if="hasVideo">
			<video
				:src="videoUrl"
				controls
				class="w-full h-full object-contain"
				@error="handleDelete" />
		</template>

		<!-- 默认图片 -->
		<template v-else>
			<img
				:src="videoUrl"
				alt="视频上传"
				class="w-full h-full object-contain cursor-pointer"
				@click="handleUploadClick" />
		</template>

		<!-- 操作按钮 -->
		<div v-if="!showOnly" class="absolute inset-0 pointer-events-none">
			<!-- 上传按钮 - 无视频时显示 -->
			<div
				v-if="!hasVideo"
				class="absolute inset-0 flex items-center justify-center pointer-events-auto cursor-pointer"
				@click="handleUploadClick">
				<div class="text-center">
					<UploadOutlined class="text-6! text-gray-500 mb-2" />
				</div>
			</div>

			<!-- 操作按钮组 - 有视频时显示，或者有撤回操作时显示 -->
			<div
				v-if="hasVideo || canRollback"
				class="absolute inset-0 flex flex-col justify-between p-1">
				<!-- 顶部按钮组 -->
				<div class="flex justify-between pointer-events-auto">
					<!-- 左上角：预览按钮 -->
					<EyeOutlined
						v-if="hasVideo"
						class="text-white bg-black/50 rounded-full p-1 hover:bg-black/70 cursor-pointer"
						@click="showPreview" />
					<!-- 占位 -->
					<div v-else class="w-6 h-6"></div>

					<!-- 右上角：上传按钮 -->
					<UploadOutlined
						class="text-white bg-black/50 rounded-full p-1 hover:bg-black/70 cursor-pointer"
						@click="handleUploadClick" />
				</div>

				<!-- 底部按钮组 -->
				<div class="flex justify-between pointer-events-auto">
					<!-- 左下角：撤回按钮 -->
					<RollbackOutlined
						v-if="canRollback"
						class="text-white bg-black/50 rounded-full p-1 hover:bg-black/70 cursor-pointer"
						@click="handleRollback" />
					<!-- 占位 -->
					<div v-else class="w-6 h-6"></div>

					<!-- 右下角：删除按钮 -->
					<DeleteOutlined
						v-if="hasVideo"
						class="text-white bg-black/50 rounded-full p-1 hover:bg-black/70 cursor-pointer"
						@click="handleDelete" />
				</div>
			</div>

			<!-- 播放按钮 -->
			<div
				v-if="hasVideo"
				class="absolute inset-0 flex items-center justify-center pointer-events-none">
				<PlayCircleOutlined class="text-8! text-white/80" />
			</div>
		</div>

		<!-- 加载状态 -->
		<div
			v-if="isUploading"
			class="absolute inset-0 flex items-center justify-center bg-black/50 pointer-events-none">
			<div class="text-white">上传中...</div>
		</div>
	</div>

	<!-- 隐藏的文件输入 -->
	<input
		ref="fileInputRef"
		type="file"
		:accept="accept"
		class="hidden"
		@change="handleFileSelect" />

	<!-- 视频预览模态框 -->
	<a-modal
		v-model:open="previewVisible"
		title="视频预览"
		:footer="null"
		width="80%"
		:closable="true"
		@cancel="handlePreviewCancel">
		<div class="flex justify-center items-center">
			<video :src="videoUrl" controls class="max-w-full max-h-[70vh]" autoplay />
		</div>
	</a-modal>
</template>
